package cn.com.headfree.ftp;

import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPReply;
import org.apache.commons.pool.PoolableObjectFactory;
import org.apache.log4j.Logger;

@SuppressWarnings("all")
public class FTPClientFactory implements PoolableObjectFactory<FTPClient> {
    private FTPProperties ftpProperties;
    private static FTPClientFactory factory;

    private static final Logger log = Logger.getLogger(FTPClientFactory.class);

    private FTPClientFactory(FTPProperties ftpProperties) {
        if (this.ftpProperties == null) {
            this.ftpProperties = ftpProperties;
        }
    }

    public static FTPClientFactory getInstance(FTPProperties ftpProperties) {
        if (FTPClientFactory.factory == null) {
            FTPClientFactory.factory = new FTPClientFactory(ftpProperties);
        }
        return factory;
    }

    @Override
    public FTPClient makeObject() throws Exception {
        FTPClient ftpClient = new FTPClient();
        ftpClient.setControlEncoding(ftpProperties.getEncoding());
        ftpClient.setConnectTimeout(ftpProperties.getClientTimeout());
        try {
            ftpClient.connect(ftpProperties.getHost(), ftpProperties.getPort());
            int reply = ftpClient.getReplyCode();
            if (!FTPReply.isPositiveCompletion(reply)) {
                ftpClient.disconnect();
                log.warn("FTPServer refused connection");
                return null;
            }
            boolean result = ftpClient.login(ftpProperties.getUsername(), ftpProperties.getPassword());
            ftpClient.setFileType(ftpProperties.getTransferFileType());
            if (!result) {
                log.warn("ftpClient login failed... username is {}" + ftpProperties.getUsername());
            }
        } catch (Exception e) {
            log.error("create ftp connection failed...{}", e);
            throw e;
        }

        return ftpClient;
    }

    @Override
    public void destroyObject(FTPClient ftpClient) throws Exception {
    	if (ftpClient != null) {
            ftpClient.disconnect();
        }
        ftpClient = null;
    }

    @Override
    public boolean validateObject(FTPClient ftpClient) {
        try {
            return ftpClient.sendNoOp();
        } catch (Exception e) {
            log.error("Failed to validate client: {}");
        }
        return false;
    }

    @Override
    public void activateObject(FTPClient obj) throws Exception {
        //Do nothing

    }

    @Override
    public void passivateObject(FTPClient obj) throws Exception {
        //Do nothing

    }
}
